using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms;
using Terminal.Advanced_AEUC_settings_controls.Settings_AUX;
using Terminal.Advanced_AEUC_settings_controls.Settings_Interfaces;
using Terminal.Advanced_AEUC_settings_controls.Settings_Editing_Forms;
using Terminal.Advanced_AEUC_settings_controls.Setting_Advanced_Control;
using System.Drawing;
using System.IO;
using System.Threading;
using ProgressBars;

namespace Terminal.Advanced_AEUC_settings_controls.Setting_Advanced_Control
{
    /// <summary>
    /// The parent control that will contain all of the tabs with specific advanced AEUC setting controls
    /// </summary>
    public class AEUCTabbedParentControl : TabControl, IAEUCSerialization
    {
        int new_tab_counter = 1;
        bool not_deserializing = true;
        /// <summary>
        /// Set to the file that the UI definitions were loaded from - used for quick saves and such
        /// </summary>
        public FileInfo fileLoadedFrom = null;
        /// <summary>
        /// AEUCTabbedParentControl child controls transmit messages via this delegate 
        /// </summary>
        public CommLink.CommLink.MessageSend sendMsg;
        /// <summary>
        /// Running with no GUI
        /// </summary>
        bool NoGUI = false;

        #region Context menu options

        const string SEND_TAB_STNGS = "Send tab settings";
        const string SET_STNGS_TO_DFT = "Set settings to default values";
        const string ROLLBACK_STNGS = "Rollback settings values";
        const string SET_STNGS_STATE_2_CHNGD = "Set settings change state to changed";
        const string ADD_NEW_STNG = "Add new setting";
        const string REMOVE_STNGS = "Remove setting";
        const string CNCL_REMOVE_STNGS = "Cancel setting removal";
        const string LINK_STNGS = "Link settings";
        const string CNCL_LINK_STNGS = "Cancel link";
        const string DCLR_AUX_STNGS = "Declare AUX settings connection";
        const string ADD_BUTTON = "Add new button";
        const string ADD_STNGS_TAB_PAGE = "Add new Parameter stucture tab";
        const string REM_STNGS_TAB_PAGE = "Remove this Parameter stucture tab";
        const string TAB_PAGE_PROP = "Parameter stucture properties";
        const string EDIT_ASSOCIATED_MESSAGES = "Edit associated messages";
        const string ALIGN_CTRLS_ON_PAGE = "Align controls";
        const string REORDER_CTRLS_ON_PAGE = "Reorder controls";
        const string SAVE_USR_STNGS = "Save user settings";
        const string SAVE_USR_STNGS_AS = "Save user settings as";
        const string LOAD_USR_STNGS = "Load user settings";
        const string ADD_OMX_STD_STRUCT_HDR = "Add OMX standard structure header";
        const string CALC_OMX_STRUCT_SIZE = "Calculate OMX structure size";
        const string SET_CTRL_ID_IN_ORDER = "Set control id's equal to control's tab page order";
        const string SAVE_CTRL_EXPORT_FILE = "Export controls to file";
        const string LOAD_CTRL_EXPORT_FILE = "Import controls from file";

        #endregion

        /// <summary>
        /// Delegate invoked when the AEUC setting controls haeuc been changed
        /// </summary>
        public delegate void AEUCControlsUpdated();
        /// <summary>
        /// Event fired when any changes to the AEUC settings controls occur
        /// </summary>
        public event AEUCControlsUpdated OnAEUCControlsUpdated;

        #region Link control flags and arrays
        bool declaring_new_link = false;
        bool destroying_old_link = false;
        /// <summary>
        /// Flag indicating if the system is waiting selection input for UI element removal
        /// </summary>
        public bool removing_aeuc_setting = false;
        bool declaring_aux_link = false;
        List<IAEUCSetting> LinkSettingsDeclaration;
        #endregion

        /// <summary>
        /// Container class with all the common message definitions and parameters
        /// </summary>
        public CommonMSGControl cmcDefinitios;
        /// <summary>
        /// List containing all of the tab page descriptors
        /// </summary>
        public List<GenTabPageProperties> gtpProperties;

        /// <summary>
        /// Delegate for handling tab page layout event
        /// </summary>
        LayoutEventHandler lehAlignControls;

        /// <summary>
        /// Empty constructor
        /// </summary>
        public AEUCTabbedParentControl(CommLink.CommLink.MessageSend incDelegate)
            : base()
        {
            sendMsg = incDelegate;
            LinkSettingsDeclaration = new List<IAEUCSetting>();
            gtpProperties = new List<GenTabPageProperties>();

            #region Context menu setup
            EventHandler eh = new EventHandler(ContextMenu);
            ContextMenuStrip =  new ContextMenuStrip();
                
            //ContextMenuStrip.Items.Add(SEND_TAB_SETTINGS, null, eh);
            ContextMenuStrip.Items.Add(SET_STNGS_TO_DFT, null, eh);
            ContextMenuStrip.Items.Add(ROLLBACK_STNGS, null, eh);
            ContextMenuStrip.Items.Add(SET_STNGS_STATE_2_CHNGD, null, eh);

            ToolStripMenuItem itmControls = new ToolStripMenuItem("Controls");
            itmControls.DropDownItems.Add(ADD_NEW_STNG, null, eh);
            itmControls.DropDownItems.Add(ADD_OMX_STD_STRUCT_HDR, null, eh);
            itmControls.DropDownItems.Add(CALC_OMX_STRUCT_SIZE, null, eh);
            itmControls.DropDownItems.Add(SET_CTRL_ID_IN_ORDER, null, eh);
            itmControls.DropDownItems.Add(REMOVE_STNGS, null, eh);
            itmControls.DropDownItems.Add(LINK_STNGS, null, eh);
            //itmControls.DropDownItems.Add(DECLARE_AUX_SETTINGS, null, eh);
            itmControls.DropDownItems.Add(ADD_BUTTON, null, eh);
            ContextMenuStrip.Items.Add(itmControls);

            ToolStripMenuItem itmTabPageOpt = new ToolStripMenuItem("Tab page options");
            //itmTabPageOpt.DropDownItems.Add(ADD_SETTINGS_TAB_PAGE, null, eh);
            //itmTabPageOpt.DropDownItems.Add(REMOVE_SETTINGS_TAB_PAGE, null, eh);
            //itmTabPageOpt.DropDownItems.Add(TAB_PAGE_PROPERTIES, null, eh);
            //itmTabPageOpt.DropDownItems.Add(EDIT_ASSOCIATED_MESSAGES, null, eh);
            itmTabPageOpt.DropDownItems.Add(ALIGN_CTRLS_ON_PAGE, null, eh);
            itmTabPageOpt.DropDownItems.Add(REORDER_CTRLS_ON_PAGE, null, eh);
            ContextMenuStrip.Items.Add(itmTabPageOpt);

            ToolStripMenuItem itmSaveOpt = new ToolStripMenuItem("Save options");
            //itmSaveOpt.DropDownItems.Add(SAVE_USR_STNGS, null, eh);
            //itmSaveOpt.DropDownItems.Add(SAVE_USR_STNGS_AS, null, eh);
            //itmSaveOpt.DropDownItems.Add(LOAD_USR_STNGS, null, eh);
            itmSaveOpt.DropDownItems.Add(SAVE_CTRL_EXPORT_FILE, null, eh);
            itmSaveOpt.DropDownItems.Add(LOAD_CTRL_EXPORT_FILE, null, eh);
            ContextMenuStrip.Items.Add(itmSaveOpt);
            #endregion

            //Multiline = true;
            //SizeMode = TabSizeMode.FillToRight;
            SizeMode = TabSizeMode.Normal;
            //if (TabPages.Count == 0)
                //AddTabPage("Default Parameter structure");

            cmcDefinitios = new CommonMSGControl(this);
            lehAlignControls = new LayoutEventHandler(AEUCTabbedParentControl_Layout);
            Selected += new TabControlEventHandler(AEUCTabbedParentControl_Selected);
        }

        #region UI control interface
        /// <summary>
        /// Adds a tab page to the user interface and associated properties.
        /// </summary>
        /// <param name="iname">Name of the new tab page</param>
        /// <returns>Index of the tab page in the user interface</returns>
        public int AddTabPage(string iname)
        {
            TabPage tmpPage = new TabPage(iname);
            tmpPage.AutoScroll = true;
            TabPages.Add(tmpPage);
            gtpProperties.Add(new GenTabPageProperties(iname,tmpPage,this));

            return TabPages.Count - 1;
        }
        /// <summary>
        /// Removes a selected tab page from the user interface and associated properties.
        /// </summary>
        /// <param name="indx">Index of the selected tab page</param>
        public void RemTabPage(int indx)
        {
            if (gtpProperties.Count > indx)
            {
                gtpProperties.RemoveAt(indx);
                TabPages.RemoveAt(indx);
            }
        }
        /// <summary>
        /// Opens a form for editting parameter tab page properties.
        /// </summary>
        /// <param name="indx">Index of the selected tab page</param>
        public void OMXStructPageProperties(int indx)
        {
            if (gtpProperties.Count > indx)
            {
                //Properties of the selected tab page
                AEUCTabPageProperties atbp = new AEUCTabPageProperties(gtpProperties[indx]);
                atbp.ShowDialog();
            }
        }
        /// <summary>
        /// Opens a form for editting OMX messaging properties.
        /// </summary>
        public void OMXSCompMessagingProperties()
        {
            AEUCMessages AEUCmsg = new AEUCMessages(this);
            AEUCmsg.ShowDialog();
        }
        /// <summary>
        /// Updates the name of a selected parameter tab page.
        /// </summary>
        /// <param name="indx">Index of the tab page</param>
        /// <param name="iName">New name of the tab page</param>
        public void OMXStructPageUpdateName(int indx, string iName)
        {
            if (gtpProperties.Count > indx)
            {
                gtpProperties[indx].TabName = iName;
            }
        }
        /// <summary>
        /// Updates the component instance Id field of a tab page.
        /// </summary>
        /// <param name="indx">Index of the tab page</param>
        /// <param name="iId">New name of the tab page</param>
        public void OMXStructPageUpdateCompInstanceId(int indx, uint iId)
        {
            if (gtpProperties.Count > indx)
            {
                gtpProperties[indx].TabRelCompId = iId;
            }
        }
        /// <summary>
        /// Clears all of the interface tab pages and associated properties.
        /// </summary>
        public void ClrTabPages()
        {
            for (int i = 0; i < TabPages.Count; i++)
            {
                TabPages[i].Dispose();
            }
            TabPages.Clear();
            TabPagesL = null;
            gtpProperties.Clear();
        }
        #endregion

        #region File save and load
        /// <summary>
        /// Local AEUCMessages object to resolve UI references
        /// </summary>
        AEUCMessages avmM;
        /// <summary>
        /// The last loaded file.
        /// </summary>
        FileInfo loadFile;
        /// <summary>
        /// Resave the user setting definitions to the file that they were loaded from.
        /// </summary>
        public void FileSave(FileInfo finf)
        {
            while (!not_deserializing);

            if (finf != null)
            {
                BinaryWriter binWrt = null;
                try
                {
                    binWrt = new BinaryWriter(finf.Create());
                    ((IAEUCSerialization)this).Serialize(binWrt);
                }
                catch (Exception ex)
                {
                    MessageBox.Show(ex.Message);
                }
                finally
                {
                    if (binWrt != null)
                        binWrt.Close();
                }
            }
        }
        /// <summary>
        /// Saves the user setting definitions to a specified file
        /// </summary>
        public void FileSaveAs()
        {
            while (!not_deserializing) ;

            SaveFileDialog sfd = new SaveFileDialog();
            sfd.AddExtension = true;
            sfd.DefaultExt = "tsd";
            sfd.Filter = "*.tsd|*.tsd";

            if (sfd.ShowDialog() == DialogResult.OK)
            {
                BinaryWriter binWrt = null;
                try
                {
                    FileInfo saveFile = new FileInfo(sfd.FileName);
                    binWrt = new BinaryWriter(saveFile.Create());
                    ((IAEUCSerialization)this).Serialize(binWrt);
                    fileLoadedFrom = saveFile;
                }
                catch (Exception ex)
                {
                    MessageBox.Show(ex.Message);
                }
                finally
                {
                    if (binWrt != null)
                        binWrt.Close();
                }
            }
        }
        /// <summary>
        /// Loads user setting definitions from a file.
        /// </summary>
        public void FileLoad()
        {
            while (!not_deserializing) ;

            OpenFileDialog ofd = new OpenFileDialog();
            ofd.DefaultExt = "tsd";
            ofd.Filter = "*.tsd|*.tsd";

            if (ofd.ShowDialog() == DialogResult.OK)
            {
                avmM = new AEUCMessages(this);
                BinaryReader binRdr = null;
                try
                {
                    loadFile = new FileInfo(ofd.FileName);
                    binRdr = new BinaryReader(loadFile.OpenRead());
                    if (loadFile.Exists)
                    {
                        ClrTabPages();
                        ((IAEUCSerialization)this).Deserialize(binRdr);
                    }
                    avmM.ReloadAllUI();
                }
                catch (Exception ex)
                {
                    loadFile = null;
                    MessageBox.Show(ex.Message);
                }
                finally
                {
                    //The deserialization function should close this file...so far...
                    //if(binRdr != null)
                        //binRdr.Close();
                }
            }
        }
        /// <summary>
        /// Loads user setting definitions from a file.
        /// </summary>
        /// <param name="fInf">FileInfo object from which to open the file to load from.</param>
        public void FileLoad(FileInfo fInf)
        {
            while (!not_deserializing) ;

            avmM = new AEUCMessages(this);
            BinaryReader binRdr = null;
            try
            {
                if (fInf.Exists)
                {
                    binRdr = new BinaryReader(fInf.OpenRead());
                    ClrTabPages();
                    ((IAEUCSerialization)this).Deserialize(binRdr);
                    loadFile = fInf;
                }
                avmM.ReloadAllUI();
            }
            catch (Exception ex)
            {
                loadFile = null;
                MessageBox.Show(ex.Message);
            }
            finally
            {
                //The deserialization function should close this file...so far...
                //if(binRdr != null)
                    //binRdr.Close();
            }
        }
        /// <summary>
        /// Save a control export file
        /// </summary>
        /// <param name="ctrlSaveLst">List of ui controls to serialize</param>
        void SaveCtrlExport(IAEUCSerialization[] ctrlSaveLst)
        {
            SaveFileDialog sfd = new SaveFileDialog();
            sfd.AddExtension = true;
            sfd.DefaultExt = "tsd";
            sfd.Filter = "*.tsd|*.tsd";

            if (sfd.ShowDialog() == DialogResult.OK)
            {
                BinaryWriter binWrt = null;
                try
                {
                    FileInfo saveFile = new FileInfo(sfd.FileName);
                    binWrt = new BinaryWriter(saveFile.Create());

                    binWrt.Write(ctrlSaveLst.Length);
                    for (int i = 0; i < ctrlSaveLst.Length; i++)
                    {
                        if (ctrlSaveLst[i].GetType() == typeof(AEUCSettingButton))
                        {
                            binWrt.Write(0);
                        }
                        else if (ctrlSaveLst[i].GetType() == typeof(AEUCSettingCheckBox))
                        {
                            binWrt.Write(1);
                        }
                        else if (ctrlSaveLst[i].GetType() == typeof(AEUCComboBox))
                        {
                            binWrt.Write(2);
                        }
                        else if (ctrlSaveLst[i].GetType() == typeof(AEUCNUD))
                        {
                            binWrt.Write(3);
                        }
                        else if (ctrlSaveLst[i].GetType() == typeof(AEUCSettingTextBox))
                        {
                            binWrt.Write(4);
                        }
                        ctrlSaveLst[i].Serialize(binWrt);
                    }
                }
                catch (Exception ex)
                {
                    MessageBox.Show(ex.Message);
                }
                finally
                {
                    binWrt.Close();
                }
            }
        }
        /// <summary>
        /// Load a control export file
        /// </summary>
        /// <returns>Array of deserialized controls</returns>
        Control[] LoadCtrlExport()
        {
            OpenFileDialog ofd = new OpenFileDialog();
            ofd.DefaultExt = "tsd";
            ofd.Filter = "*.tsd|*.tsd";
            List<Control> ctrlImportLst = new List<Control>();

            if (ofd.ShowDialog() == DialogResult.OK)
            {
                AEUCMessages avmM = new AEUCMessages(this);
                BinaryReader binRdr = null;
                try
                {
                    FileInfo loadFile = new FileInfo(ofd.FileName);
                    binRdr = new BinaryReader(loadFile.OpenRead());
                    if (loadFile.Exists)
                    {
                        int ctrlNum = binRdr.ReadInt32();

                        for (int i = 0; i < ctrlNum; i++)
                        {
                            Control ctrTmp = null;
                            switch (binRdr.ReadInt32())
                            {
                                case 0:
                                    ctrTmp = new AEUCSettingButton(this);
                                    break;
                                case 1:
                                    ctrTmp = new AEUCSettingCheckBox();
                                    break;
                                case 2:
                                    ctrTmp = new AEUCComboBox();
                                    break;
                                case 3:
                                    ctrTmp = new AEUCNUD();
                                    break;
                                case 4:
                                    ctrTmp = new AEUCSettingTextBox();
                                    break;
                                default:
                                    throw new Exception("Error reading control export file!");
                            }
                            ((IAEUCSerialization)ctrTmp).Deserialize(binRdr);
                            ctrlImportLst.Add(ctrTmp);
                        }
                    }
                    avmM.ReloadAllUI();
                }
                catch (Exception ex)
                {
                    MessageBox.Show(ex.Message);
                }
                finally
                {
                    binRdr.Close();
                }
            }

            return ctrlImportLst.ToArray();
        }
        /// <summary>
        /// Export Commom message definitions to a file
        /// </summary>
        public void SaveCMCExport()
        {
            SaveFileDialog sfd = new SaveFileDialog();
            sfd.AddExtension = true;
            sfd.DefaultExt = "tsd";
            sfd.Filter = "*.tsd|*.tsd";

            if (sfd.ShowDialog() == DialogResult.OK)
            {
                BinaryWriter binWrt = null;
                try
                {
                    FileInfo saveFile = new FileInfo(sfd.FileName);
                    binWrt = new BinaryWriter(saveFile.Create());

                    cmcDefinitios.Serialize(binWrt);
                }
                catch (Exception ex)
                {
                    MessageBox.Show(ex.Message);
                }
                finally
                {
                    binWrt.Close();
                }
            }
        }
        /// <summary>
        /// Imports Common message definitions from a file
        /// </summary>
        public void LoadCMCExport()
        {
            OpenFileDialog ofd = new OpenFileDialog();
            ofd.DefaultExt = "tsd";
            ofd.Filter = "*.tsd|*.tsd";
            List<Control> ctrlImportLst = new List<Control>();

            if (ofd.ShowDialog() == DialogResult.OK)
            {
                BinaryReader binRdr = null;
                try
                {
                    FileInfo loadFile = new FileInfo(ofd.FileName);
                    binRdr = new BinaryReader(loadFile.OpenRead());
                    if (loadFile.Exists)
                    {
                        if (cmcDefinitios.Deserialize(binRdr))
                        {
                            #region Common message definitions message resets
                            for (int i = 0; i < cmcDefinitios.AEUC_MSG.Count; i++)
                            {
                                ((GenMSG)cmcDefinitios.AEUC_MSG[i]).ResetMessageControlTabReferences(TabPagesL);
                            }
                            for (int i = 0; i < cmcDefinitios.SPECMSG_MSG.Count; i++)
                            {
                                ((GenMSG)cmcDefinitios.SPECMSG_MSG[i]).ResetMessageControlTabReferences(TabPagesL);
                            }
                            #endregion
                            #region AEUC setting linking and auxiliary reference resets
                            for (int i = 0; i < TabPages.Count; i++)
                            {
                                for (int ctrReset = 0; ctrReset < TabPages[i].Controls.Count; ctrReset++)
                                {
                                    if (TabPages[i].Controls[ctrReset].GetType() == typeof(AEUCSettingButton))
                                    {
                                        ((AEUCSettingButton)TabPages[i].Controls[ctrReset]).ResetMessageReference(cmcDefinitios);
                                    }
                                }
                            }
                            #endregion
                        }
                    }
                }
                catch (Exception ex)
                {
                    MessageBox.Show(ex.Message);
                }
                finally
                {
                    binRdr.Close();
                }
            }
        }
        /// <summary>
        /// Running with no GUI
        /// </summary>
        /// <param name="enable">GUI enabled statuse</param>
        public void RunningNoGUI(bool noGUI)
        {
            NoGUI = noGUI;
        }
        #endregion

        #region Context menu handlers
        /// <summary>
        /// Context menu function
        /// </summary>
        new void ContextMenu(object sender, EventArgs ea)
        {
            ToolStripItem tmpItem = (ToolStripItem)sender;
            if (tmpItem.Text == ADD_NEW_STNG)
            {
                if (TabPages.Count > 0 && SelectedIndex > -1)
                {
                    AEUCCreateSettings acs = new AEUCCreateSettings(this);
                    acs.ShowDialog();

                    if (OnAEUCControlsUpdated != null)
                        OnAEUCControlsUpdated();
                }
            }
            else if (tmpItem.Text == ADD_STNGS_TAB_PAGE)
            {
                AddTabPage("Default Parameter structure " + new_tab_counter++.ToString());
                SelectedIndex = TabPages.Count - 1;
            }
            else if (tmpItem.Text == REM_STNGS_TAB_PAGE)
            {
                RemTabPage(SelectedIndex);
                if (TabPages.Count == 0)
                    AddTabPage("Default Parameter structure");
            }
            else if (tmpItem.Text == TAB_PAGE_PROP)
            {
                //Properties of the selected tab page
                AEUCTabPageProperties atbp = new AEUCTabPageProperties(gtpProperties[SelectedIndex]);
                atbp.ShowDialog();
            }
            else if (tmpItem.Text == EDIT_ASSOCIATED_MESSAGES)
            {
                AEUCMessages AEUCmsg = new AEUCMessages(this);
                AEUCmsg.ShowDialog();
            }
            else if (tmpItem.Text == SET_STNGS_TO_DFT)
            {
                for (int i = 0; i<TabPages[SelectedIndex].Controls.Count; i++)
                {
                    if (TabPages[SelectedIndex].Controls[i] is IAEUCSetting)
                        ((IAEUCSetting)TabPages[SelectedIndex].Controls[i]).AEUC_ResetToDefault();
                }
            }
            else if (tmpItem.Text == ROLLBACK_STNGS)
            {
                for (int i = 0; i<TabPages[SelectedIndex].Controls.Count; i++)
                {
                    if (TabPages[SelectedIndex].Controls[i] is IAEUCSetting)
                        ((IAEUCSetting)TabPages[SelectedIndex].Controls[i]).AEUC_RestoreShadowedValue();
                }
            }
            else if (tmpItem.Text == SET_STNGS_STATE_2_CHNGD)
            {
                for (int i = 0; i<TabPages[SelectedIndex].Controls.Count; i++)
                {
                    if (TabPages[SelectedIndex].Controls[i] is IAEUCSetting)
                        ((IAEUCSetting)TabPages[SelectedIndex].Controls[i]).AEUC_SetStateChange(true);
                }
            }
            else if (tmpItem.Text == LINK_STNGS)
            {
                tmpItem.Text = CNCL_LINK_STNGS;
                InitiateLinkGroupOperation(true);
            }
            else if (tmpItem.Text == CNCL_LINK_STNGS)
            {
                #region Cencel linking declarations
                tmpItem.Text = LINK_STNGS;
                CancelLinkGroupCreation();
                #endregion
            }
            else if (tmpItem.Text == "Destroy linked AEUC settings")
            {
                #region Destroy linked settings
                InitiateLinkGroupOperation(false);
                #endregion
            }
            else if (tmpItem.Text == DCLR_AUX_STNGS)
            {
                InitializeAUXLink();
            }
            else if (tmpItem.Text == SEND_TAB_STNGS)
            {
                // Do send code here!
            }
            else if (tmpItem.Text == ADD_BUTTON)
            {
                #region Add new button
                AEUCSettingButton asb = new AEUCSettingButton(this);
                if (TabPages[SelectedIndex].Controls.Count > 0)
                {
                    asb.Location = determineControlPosition(asb);
                }
                TabPages[SelectedIndex].Controls.Add(asb);

                AEUCButtonEditForm abef = new AEUCButtonEditForm(asb);
                abef.ShowDialog();
                #endregion
            }
            else if (tmpItem.Text == REMOVE_STNGS)
            {
                tmpItem.Text = CNCL_REMOVE_STNGS;
                InitiateSettingRemoval();
            }
            else if (tmpItem.Text == CNCL_REMOVE_STNGS)
            {
                tmpItem.Text = REMOVE_STNGS;
                CancelSettingRemoval();
            }
            else if (tmpItem.Text == REORDER_CTRLS_ON_PAGE)
            {
                CtrlReOrder cro = new CtrlReOrder(this);
                cro.ShowDialog();

                if (OnAEUCControlsUpdated != null)
                    OnAEUCControlsUpdated();
            }
            else if (tmpItem.Text == ALIGN_CTRLS_ON_PAGE)
            {
                alignControls(TabPages[SelectedIndex]);
            }
            else if (tmpItem.Text == LOAD_USR_STNGS)
            {
                FileLoad();
            }
            else if (tmpItem.Text == SAVE_USR_STNGS_AS)
            {
                FileSaveAs();
            }
            else if (tmpItem.Text == SAVE_USR_STNGS)
            {
                if (fileLoadedFrom != null)
                    FileSave(fileLoadedFrom);
                else
                    FileSaveAs();
            }
            else if (tmpItem.Text == ADD_OMX_STD_STRUCT_HDR)
            {
                #region OMX structure standard header
                uint indexes = 0;
                Control rdyControl = null;
                rdyControl = new Terminal.Advanced_AEUC_settings_controls.Setting_Advanced_Control.AEUCNUD(indexes++, 4, 0, 0, 0, 0xFFFFFFFF, true, false, false, "nSize");
                rdyControl.Location = determineControlPosition(rdyControl);
                TabPages[SelectedIndex].Controls.Add(rdyControl);

                rdyControl = null;
                rdyControl = new Terminal.Advanced_AEUC_settings_controls.Setting_Advanced_Control.AEUCNUD(indexes++, 1, 1, 1, 0, 1, true, false, false, "nVersionMajor");
                rdyControl.Location = determineControlPosition(rdyControl);
                TabPages[SelectedIndex].Controls.Add(rdyControl);

                rdyControl = null;
                rdyControl = new Terminal.Advanced_AEUC_settings_controls.Setting_Advanced_Control.AEUCNUD(indexes++, 1, 1, 1, 0, 1, true, false, false, "nVersionMinor");
                rdyControl.Location = determineControlPosition(rdyControl);
                TabPages[SelectedIndex].Controls.Add(rdyControl);

                rdyControl = null;
                rdyControl = new Terminal.Advanced_AEUC_settings_controls.Setting_Advanced_Control.AEUCNUD(indexes++, 1, 0, 0, 0, 1, true, false, false, "nRevision");
                rdyControl.Location = determineControlPosition(rdyControl);
                TabPages[SelectedIndex].Controls.Add(rdyControl);

                rdyControl = null;
                rdyControl = new Terminal.Advanced_AEUC_settings_controls.Setting_Advanced_Control.AEUCNUD(indexes++, 1, 0, 0, 0, 0, true, false, false, "nStep");
                rdyControl.Location = determineControlPosition(rdyControl);
                TabPages[SelectedIndex].Controls.Add(rdyControl);

                rdyControl = null;
                rdyControl = new Terminal.Advanced_AEUC_settings_controls.Setting_Advanced_Control.AEUCNUD(indexes++, 4, 0, 0, 0, 0xFFFFFFFF, true, false, false, "nPortIndex");
                rdyControl.Location = determineControlPosition(rdyControl);
                TabPages[SelectedIndex].Controls.Add(rdyControl);
                #endregion

                if (OnAEUCControlsUpdated != null)
                    OnAEUCControlsUpdated();
            }
            else if(tmpItem.Text == SAVE_CTRL_EXPORT_FILE)
            {
                IAEUCSerialization[] ctrlSaveLst = new IAEUCSerialization[TabPages[SelectedIndex].Controls.Count];
                for (int i = 0; i < TabPages[SelectedIndex].Controls.Count; i++)
                {
                    ctrlSaveLst[i] = (IAEUCSerialization)TabPages[SelectedIndex].Controls[i];
                }
                SaveCtrlExport(ctrlSaveLst);
            }
            else if (tmpItem.Text == LOAD_CTRL_EXPORT_FILE)
            {
                Control[] ctrlList = LoadCtrlExport();
                if (ctrlList != null)
                {
                    for (int ikT = 0; ikT < ctrlList.Length; ikT++)
                    {
                        ctrlList[ikT].Location = determineControlPosition(ctrlList[ikT]);
                    }
                    TabPages[SelectedIndex].Controls.AddRange(ctrlList);
                }
            }
            else if (tmpItem.Text == CALC_OMX_STRUCT_SIZE)
            {
                int structSize = 0;
                for (int i = 0; i < TabPages[SelectedIndex].Controls.Count; i++)
                {
                    structSize += (int)((IAEUCSetting)TabPages[SelectedIndex].Controls[i]).AEUC_Size;
                }
                MessageBox.Show("Struct size: " + structSize.ToString());
            }
            else if (tmpItem.Text == SET_CTRL_ID_IN_ORDER)
            {
                for (int i = 0; i < TabPages[SelectedIndex].Controls.Count; i++)
                {
                    if (TabPages[SelectedIndex].Controls[i] is IAEUCSetting)
                    {
                        ((IAEUCSetting)TabPages[SelectedIndex].Controls[i]).AEUC_Id = (uint)i;
                    }
                }
            }
        }
        #endregion

        #region Control positions
        /// <summary>
        /// Functions determines where on the tab the newly created control should be placed
        /// </summary>
        /// <param name="ctrlToPlace">The control which location is to be determined</param>
        /// <returns>The point where the location of the control should be</returns>
        public Point determineControlPosition(Control ctrlToPlace)
        {
            Point nCtrPos = new Point(0, 0);
            bool no_space_available = false;

            if (TabPages[SelectedIndex].Controls.Count > 0)
            {
                Control tmpCont = TabPages[SelectedIndex].Controls[TabPages[SelectedIndex].Controls.Count - 1];
                nCtrPos = new Point(tmpCont.Location.X, tmpCont.Location.Y + tmpCont.Size.Height + 3);
                if ((tmpCont.Location.Y + tmpCont.Size.Height + ctrlToPlace.Size.Height + 3) > TabPages[SelectedIndex].Size.Height)
                {
                    Point cmprPos = new Point(0, 0);
                    Size cmprSize = new Size(0, 0);

                    cmprPos = TabPages[SelectedIndex].Controls[0].Location;
                    cmprSize = TabPages[SelectedIndex].Controls[0].Size;

                    for (int i = 1; i < TabPages[SelectedIndex].Controls.Count - 1; i++)
                    {
                        if (TabPages[SelectedIndex].Controls[i].Location.X > cmprPos.X)
                        {
                            cmprPos = TabPages[SelectedIndex].Controls[i].Location;
                            cmprSize = TabPages[SelectedIndex].Controls[i].Size;
                        }
                    }

                    if (cmprPos.X > nCtrPos.X + tmpCont.Size.Width)
                    {
                        if (cmprPos.Y + cmprSize.Height + 3 < TabPages[SelectedIndex].Size.Height)
                            nCtrPos = new Point(cmprPos.X, cmprPos.Y + cmprSize.Height + 3);
                        else
                            no_space_available = true;
                    }
                    else
                    {
                        if (cmprPos.X + cmprSize.Width + 3 < TabPages[SelectedIndex].Size.Width)
                            nCtrPos = new Point(cmprPos.X + cmprSize.Width + 3, cmprPos.Y);
                        else
                            no_space_available = true;
                    }
                }
            }

            if (!eligibleLocationHitTest(TabPages[SelectedIndex].Controls, nCtrPos, ctrlToPlace.Size) || no_space_available)
            {
                int i = 0;
                int k = 0;
                if (nCtrPos.X < TabPages[SelectedIndex].Size.Width - ctrlToPlace.Size.Width)
                    i = nCtrPos.X;
                if (nCtrPos.Y < TabPages[SelectedIndex].Size.Height - ctrlToPlace.Size.Height)
                    k = nCtrPos.Y;

                for (; i < TabPages[SelectedIndex].Size.Width - ctrlToPlace.Size.Width; i++)
                {
                    for (; k < TabPages[SelectedIndex].Size.Height - ctrlToPlace.Size.Height; k++)
                    {
                        nCtrPos = new Point(i, k);
                        if (!(k < TabPages[SelectedIndex].Size.Height - ctrlToPlace.Size.Height))
                            k = 0;
                        else if (eligibleLocationHitTest(TabPages[SelectedIndex].Controls, nCtrPos, ctrlToPlace.Size))
                            return nCtrPos;
                    }
                    if (!(i < TabPages[SelectedIndex].Size.Width - ctrlToPlace.Size.Width))
                        i = 0;
                }
            }

            return nCtrPos;
        }
        /// <summary>
        /// Tests if a suggested control location within a tab page is acceptable
        /// </summary>
        /// <param name="ctrlTest">All of the controls belonging to the same tab page as the proposed location test</param>
        /// <param name="ptTest">Top left location of the cotnrol for test</param>
        /// <param name="szTest">Size of the control for test</param>
        /// <returns>True if the proposed location doesn't overlap with any other control</returns>
        public bool eligibleLocationHitTest(Control.ControlCollection ctrlTest, Point ptTest, Size szTest)
        {
            for (int i = 0; i<ctrlTest.Count; i++)
            {
                if (ctrlTest[i].Location.X > ptTest.X && ctrlTest[i].Location.X < ptTest.X + szTest.Width)
                    return false;
                if (ctrlTest[i].Location.X < ptTest.X && ctrlTest[i].Location.X + ctrlTest[i].Size.Width > ptTest.X)
                    return false;
                if (ctrlTest[i].Location.Y > ptTest.Y && ctrlTest[i].Location.Y < ptTest.Y + szTest.Height)
                    return false;
                if (ctrlTest[i].Location.Y < ptTest.Y && ctrlTest[i].Location.Y + ctrlTest[i].Size.Height > ptTest.Y)
                    return false;
            }
            return true;
        }

        /// <summary>
        /// Aligns the controls - top left relative
        /// </summary>
        public void alignControls(TabPage tabP)
        {
            Point nCtrPos;
            Point xOrigCont = new Point(0,0);

            for (int i = 0; i < tabP.Controls.Count; i++)
            {
                if (i > 0)
                {
                    Control tmpCont = tabP.Controls[i - 1];
                    nCtrPos = new Point(tmpCont.Location.X, tmpCont.Location.Y + tmpCont.Size.Height + 3);

                    if (nCtrPos.Y + tabP.Controls[i].Size.Height + 3 > tabP.Size.Height)
                    {
                        nCtrPos = xOrigCont;
                        xOrigCont = new Point(0, 0);
                    }
                }
                else
                {
                    nCtrPos = new Point(3, 3);
                }

                tabP.Controls[i].Location = nCtrPos;

                if (xOrigCont.X == 0 && xOrigCont.Y == 0)
                {
                    xOrigCont = new Point(tabP.Controls[i].Location.X + tabP.Controls[i].Size.Width + 3, tabP.Controls[i].Location.Y);
                }
                else if (tabP.Controls[i].Location.X + tabP.Controls[i].Size.Width + 3 > xOrigCont.X)
                {
                    xOrigCont = new Point(tabP.Controls[i].Location.X + tabP.Controls[i].Size.Width + 3, xOrigCont.Y);
                }
            }
        }
        #endregion

        #region Link group control section
        void ChildClickHandlerLinkGroup(object sender, MouseEventArgs e)
        {
            if (sender is IAEUCSetting)
            {
                IAEUCSetting focusedControl = ((IAEUCSetting)sender).AEUC_GetLinkReference();

                if (declaring_new_link)
                {
                    if (focusedControl.AEUC_LinkedSetting)
                    {
                        DialogResult tstCondition = MessageBox.Show("This control is already included in a link group.\n\nDo you want to destroy that link group\nand include the control in the current selection?", "Link group intersection", MessageBoxButtons.YesNoCancel);
                        if (tstCondition == DialogResult.Yes)
                        {
                            DestroyLinkedGroup(focusedControl);
                            AddControlToLinkGroupDeclaration(focusedControl);
                        }
                        else if (tstCondition == DialogResult.No)
                        {
                            MessageBox.Show("Please select another control.", "Link group intersection");
                        }
                        else if (tstCondition == DialogResult.Cancel)
                        {
                            CancelLinkGroupCreation();
                        }
                    }
                    else
                    {
                        AddControlToLinkGroupDeclaration(focusedControl);
                    }
                }
                else if (destroying_old_link)
                {
                    DestroyLinkedGroup(focusedControl);
                }
                else if (removing_aeuc_setting)
                {
                    if (focusedControl.AEUC_LinkedSetting)
                        DestroyLinkedGroup(focusedControl);

                    ((Control)sender).Parent.Controls.Remove((Control)sender);
                    ((Control)sender).Parent = null;

                    if (OnAEUCControlsUpdated != null)
                        OnAEUCControlsUpdated();
                }
            }
            else
            {
                if (removing_aeuc_setting)
                {

                    ((Control)sender).Parent.Controls.Remove((Control)sender);
                    ((Control)sender).Parent = null;

                    if (OnAEUCControlsUpdated != null)
                        OnAEUCControlsUpdated();
                }
            }
        }

        void CreateLinkGroup()
        {
            AEUCLinkSettings als = new AEUCLinkSettings(LinkSettingsDeclaration);
            als.ShowDialog();

            CancelLinkGroupCreation();

            if (OnAEUCControlsUpdated != null)
                OnAEUCControlsUpdated();
        }

        void InitiateLinkGroupOperation(bool create)
        {
            if (create)
            {
                declaring_new_link = true;
            }
            else
            {
                destroying_old_link = true;
            }
            LinkSettingsDeclaration.Clear();
            for (int i = 0; i<TabPages[SelectedIndex].Controls.Count; i++)
            {
                if (TabPages[SelectedIndex].Controls[i] is IAEUCSetting)
                    TabPages[SelectedIndex].Controls[i].MouseClick += new MouseEventHandler(ChildClickHandlerLinkGroup);
            }
        }

        void CancelLinkGroupCreation()
        {
            declaring_new_link = false;
            LinkSettingsDeclaration.Clear();
            for (int i = 0; i<TabPages[SelectedIndex].Controls.Count; i++)
            {
                if (TabPages[SelectedIndex].Controls[i] is IAEUCSetting)
                    TabPages[SelectedIndex].Controls[i].MouseClick -= new MouseEventHandler(ChildClickHandlerLinkGroup);
            }
        }

        void AddControlToLinkGroupDeclaration(IAEUCSetting addControl)
        {
            if (LinkSettingsDeclaration.Count > 0)
            {
                if (LinkSettingsDeclaration.Count > 1 && LinkSettingsDeclaration[0] == addControl)
                    CreateLinkGroup();
                else if (LinkSettingsDeclaration.Contains(addControl))
                    MessageBox.Show("This control is already selected.\nTo end the link select the first control in the link group.");
                else
                    LinkSettingsDeclaration.Add(addControl);
            }
            else
                LinkSettingsDeclaration.Add(addControl);
        }

        void DestroyLinkedGroup(IAEUCSetting entryPoint)
        {
            while (entryPoint != null)
            {
                IAEUCSetting nextPoint = entryPoint.AEUC_NextSettingLink;
                entryPoint.AEUC_NextSettingLink = null;
                entryPoint.AEUC_LinkedSetting = false;
                entryPoint = nextPoint;
            }
            destroying_old_link = false;
        }
        #endregion

        #region Remove AEUC setting
        void InitiateSettingRemoval()
        {
            removing_aeuc_setting = true;
            for (int i = 0; i<TabPages[SelectedIndex].Controls.Count; i++)
            {
                TabPages[SelectedIndex].Controls[i].MouseClick += new MouseEventHandler(ChildClickHandlerLinkGroup);
            }
        }

        void CancelSettingRemoval()
        {
            removing_aeuc_setting = false;
            for (int i = 0; i<TabPages[SelectedIndex].Controls.Count; i++)
            {
                TabPages[SelectedIndex].Controls[i].MouseClick -= new MouseEventHandler(ChildClickHandlerLinkGroup);
            }
        }
        #endregion

        #region Map auxiliary control with controls to set
        void ChildClickHandlerAUXLink(object sender, MouseEventArgs e)
        {
            IAEUCSetting focusedControl = (IAEUCSetting)sender;

            // If this is the second aux link control
            //that will end the aux linkdeclarationa 
            //and will be mapped to the secondary setting
            //of the aux control
            if(LinkSettingsDeclaration.Count == 2)
            {
                LinkSettingsDeclaration.Add(focusedControl);
                CommitAuxLink();
            }
            //If adding the first item that will be the auxiliary control or
            //if this will be the first aux link control
            //associated with the primary setting of the aux control
            else
            {
                LinkSettingsDeclaration.Add(focusedControl);
                if (LinkSettingsDeclaration.Count == 1)
                    MessageBox.Show("Please select the control that'll be mapped to the primary setting value.", "AUX link declaration");
                else
                    MessageBox.Show("Please select the control that'll be mapped to the secondary setting value.", "AUX link declaration");
            }
        }

        void InitializeAUXLink()
        {
            declaring_aux_link = true;
            LinkSettingsDeclaration.Clear();
            for (int i = 0; i<TabPages[SelectedIndex].Controls.Count; i++)
            {
                TabPages[SelectedIndex].Controls[i].MouseClick += new MouseEventHandler(ChildClickHandlerAUXLink);
            }
            MessageBox.Show("Please select auxiliary control.", "AUX link declaration");
        }

        void CancelAUXLink()
        {
            declaring_aux_link = false;
            LinkSettingsDeclaration.Clear();
            for (int i = 0; i<TabPages[SelectedIndex].Controls.Count; i++)
            {
                TabPages[SelectedIndex].Controls[i].MouseClick -= new MouseEventHandler(ChildClickHandlerAUXLink);
            }
        }

        void CommitAuxLink()
        {
            LinkSettingsDeclaration[0].AEUC_AUXSetting = true;
            LinkSettingsDeclaration[0].AEUC_SettingPrimaryLink = LinkSettingsDeclaration[1];
            LinkSettingsDeclaration[0].AEUC_SettingSecondaryLink = LinkSettingsDeclaration[2];
            CancelAUXLink();
        }
        #endregion

        /// <summary>
        /// Whenever a control is added to the AEUC tabbed parent it notifies the info panel to update its contents
        /// </summary>
        /// <param name="e">Control event arguments</param>
        protected override void OnControlAdded(ControlEventArgs e)
        {
            base.OnControlAdded(e);
            if (not_deserializing && OnAEUCControlsUpdated != null)
                OnAEUCControlsUpdated();
        }

        /// <summary>
        /// When a tab page is selected attach a delegate to the layout event
        /// </summary>
        /// <param name="sender">Event sender</param>
        /// <param name="e">Event parameters</param>
        private void AEUCTabbedParentControl_Selected(object sender, TabControlEventArgs e)
        {
            Layout += lehAlignControls;
        }

        /// <summary>
        /// When a tab page is about to do its layout align controls and remove the delage
        /// </summary>
        /// <param name="sender">Event sender</param>
        /// <param name="e">Event parameters</param>
        private void AEUCTabbedParentControl_Layout(object sender, LayoutEventArgs e)
        {
            Layout -= lehAlignControls;
            alignControls(TabPages[SelectedIndex]);
        }

        #region Progress bar on element deserialization

        ProgBarsDisp progDisplay;

        delegate ProgBarsDisp CreateBarsDispDelegare();

        /// <summary>
        /// Initializes progress bars display for this window
        /// </summary>
        /// <returns>Progress bars instance reference</returns>
        public ProgBarsDisp initProgBarsDisplay()
        {
            if (InvokeRequired)
            {
                Invoke(new CreateBarsDispDelegare(initProgBarsDisplay));
            }
            else
            {
                progDisplay = new ProgBarsDisp();
                progDisplay.Parent = this.Parent;
                progDisplay.Location = new Point(0, 0);
                progDisplay.BringToFront();
                progDisplay.Dock = DockStyle.Fill;
            }

            return progDisplay;
        }

        delegate void DestroyBarsDispDelegare(ProgBarsDisp progDisplay);

        /// <summary>
        /// Destroys an active progress bars instance on this window
        /// </summary>
        /// <param name="progDisplay">Progress bars instance reference</param>
        public void destroyProgBarsDisplay(ProgBarsDisp progDisplay)
        {
            if (InvokeRequired)
            {
                BeginInvoke(new DestroyBarsDispDelegare(destroyProgBarsDisplay), new object[] { progDisplay });
            }
            else
            {
                if (progDisplay != null)
                {
                    progDisplay.Parent = null;
                    progDisplay.Dispose();
                }
            }
        }

        #endregion

        #region ISerialization Members
        /// <summary>
        /// Current element serialization state version
        /// </summary>
        public int serVersion
        {
            get
            {
                return 0x000;
            }
        }
        /// <summary>
        /// Temporary array of tab pages - used for serialization purposes
        /// </summary>
        public TabPage[] TabPagesL;
        /// <summary>
        /// Function invoked when the deserialized thread is done populating the TabPagesL array.
        /// </summary>
        void DoneDeserialization()
        {
            if (InvokeRequired)
            {
                BeginInvoke(new AEUCControlsUpdated(DoneDeserialization));
            }
            else
            {
                if (TabPagesL != null)
                    TabPages.AddRange(TabPagesL);

                #region AEUC setting linking and auxiliary reference resets
                for (int i = 0; i < TabPages.Count; i++)
                {
                    for (int ctrReset = 0; ctrReset < TabPages[i].Controls.Count; ctrReset++)
                    {
                        if (TabPages[i].Controls[ctrReset].GetType() == typeof(AEUCSerializableButton))
                        {
                            int iRefMsg = -1;
                            string btnName = "Button";
                            Point iLoc = new Point(0, 0);
                            AEUCSettingButton tmpBtn = new AEUCSettingButton(this);
                            ((AEUCSerializableButton)TabPages[i].Controls[ctrReset]).GetButtonInformation(out iRefMsg, out btnName, out iLoc);
                            tmpBtn.associate_message_reference = iRefMsg;
                            tmpBtn.SetButtonName = btnName;
                            tmpBtn.Location = iLoc;
                            tmpBtn.ResetMessageReference(cmcDefinitios);
                            TabPages[i].Controls.RemoveAt(ctrReset);
                            TabPages[i].Controls.Add(tmpBtn);
                        }
                        else if (TabPages[i].Controls[ctrReset].GetType() == typeof(AEUCComboBox))
                        {
                            ((AEUCComboBox)TabPages[i].Controls[ctrReset]).InitSizingWatch();
                        }
                    }
                }
                #endregion

                fileLoadedFrom = loadFile;

                avmM.ReloadAllUI();

                if (OnAEUCControlsUpdated != null)
                    OnAEUCControlsUpdated();

                destroyProgBarsDisplay(progDisplay);
                not_deserializing = true;
            }
        }
        /// <summary>
        /// Function invoked when the deserialized thread is done populating the TabPagesL array.
        /// </summary>
        void DoneDeserializationNoUI()
        {
            fileLoadedFrom = loadFile;

            avmM.ReloadAllUI();

            if (OnAEUCControlsUpdated != null)
                OnAEUCControlsUpdated();

            not_deserializing = true;
        }
        /// <summary>
        /// Saves this objec instance to a file
        /// </summary>
        /// <param name="srWriter">Binray writer of the associated file</param>
        void IAEUCSerialization.Serialize(System.IO.BinaryWriter srWriter)
        {
            srWriter.Write(serVersion);
            Serialize_v000(srWriter);
        }
        /// <summary>
        /// Loads this objects instance from a file
        /// </summary>
        /// <param name="srReader">Binray reader of the associated file</param>
        /// <returns>Boolean representing the success of the operation</returns>
        bool IAEUCSerialization.Deserialize(System.IO.BinaryReader srReader)
        {
            bool desProcState;
            int serialVer = srReader.ReadInt32();
            Thread deserialization = null;

            if (!not_deserializing)
            {
                while (true) ;
            }

            switch (serialVer)
            {
                case 0x000:
                    deserialization = new Thread(new ParameterizedThreadStart(LaunchDeserialize_v000));
                    desProcState = true;
                    break;
                default:
                    desProcState = false;
                    break;
            }

            if (desProcState)
            {
                progDisplay = initProgBarsDisplay();
                deserialization.IsBackground = true;
                deserialization.Start(srReader);
            }

            return desProcState;
        }

        #region Version 0x000 serialization
        void LaunchDeserialize_v000(object srReader)
        {
            bool result = Deserialize_v000((BinaryReader)srReader);
        }
        /// <summary>
        /// Version 0x000 serialization
        /// </summary>
        /// <param name="srWriter">File writer</param>
        void Serialize_v000(BinaryWriter srWriter)
        {
            cmcDefinitios.Serialize(srWriter);

            if (TabPages.Count > 0)
            {
                srWriter.Write(TabPages.Count);
                for (int i = 0; i < TabPages.Count; i++)
                {
                    srWriter.Write(TabPages[i].Text);
                    srWriter.Write(TabPages[i].Controls.Count);
                    for (int ctrlList = 0; ctrlList < TabPages[i].Controls.Count; ctrlList++)
                    {
                        #region Save the control type
                        if ((TabPages[i].Controls[ctrlList]).GetType() == typeof(AEUCSettingButton))
                        {
                            srWriter.Write(0);
                        }
                        else if ((TabPages[i].Controls[ctrlList]).GetType() == typeof(AEUCSettingCheckBox))
                        {
                            srWriter.Write(1);
                        }
                        else if ((TabPages[i].Controls[ctrlList]).GetType() == typeof(AEUCComboBox))
                        {
                            srWriter.Write(2);
                        }
                        else if ((TabPages[i].Controls[ctrlList]).GetType() == typeof(AEUCNUD))
                        {
                            srWriter.Write(3);
                        }
                        else if ((TabPages[i].Controls[ctrlList]).GetType() == typeof(AEUCSettingTextBox))
                        {
                            srWriter.Write(4);
                        }
                        #endregion
                        ((IAEUCSerialization)TabPages[i].Controls[ctrlList]).Serialize(srWriter);
                    }
                }
            }
            else
            {
                srWriter.Write(-1);
            }

            if (gtpProperties.Count > 0)
            {
                srWriter.Write(gtpProperties.Count);

                for (int i = 0; i < gtpProperties.Count; i++)
                {
                    gtpProperties[i].Serialize(srWriter);
                }
            }
            else
            {
                srWriter.Write(-1);
            }
        }
        /// <summary>
        /// Version 0x000 deserialization
        /// </summary>
        /// <param name="srReader">File reader</param>
        /// <returns>True if operation is succesful</returns>
        bool Deserialize_v000(BinaryReader srReader)
        {
            bool NoError = true;
            int specCaseLoad;
            not_deserializing = false;
            int TabPagesNum = 0;

            cmcDefinitios = new CommonMSGControl(this);

            try
            {
                NoError = cmcDefinitios.Deserialize(srReader);

                specCaseLoad = srReader.ReadInt32();
                TabPagesNum = specCaseLoad;
                if (TabPagesNum > -1)
                {
                    TabPagesL = new TabPage[TabPagesNum];
                    for (int i = 0; i < TabPagesNum; i++)
                    {
                        TabPagesL[i] = new TabPage(srReader.ReadString());
                        ProgBarsHdl tmpProgBar = null;
                        if (!NoGUI)
                            tmpProgBar = progDisplay.CreateProgressBar(TabPagesL[i].Text);


                        TabPagesL[i].AutoScroll = true;
                        int numCtrl = srReader.ReadInt32();

                        if (!NoGUI)
                        {
                            tmpProgBar.SetMaximum(numCtrl);
                            tmpProgBar.SetMinimum(0);
                            tmpProgBar.SetStep(1);
                        }
                        for (int CtrlList = 0; CtrlList < numCtrl; CtrlList++)
                        {
                            Control toAdd;
                            #region Reading the control type
                            switch (srReader.ReadInt32())
                            {
                                case 0:
                                    toAdd = new AEUCSerializableButton();
                                    break;
                                case 1:
                                    toAdd = new AEUCSettingCheckBox();
                                    break;
                                case 2:
                                    toAdd = new AEUCComboBox();
                                    break;
                                case 3:
                                    toAdd = new AEUCNUD();
                                    break;
                                case 4:
                                    toAdd = new AEUCSettingTextBox();
                                    break;
                                default:
                                    toAdd = null;
                                    break;
                            }
                            #endregion
                            if (toAdd != null)
                            {
                                NoError = ((IAEUCSerialization)toAdd).Deserialize(srReader);
                                TabPagesL[i].Controls.Add(toAdd);
                            }
                            else
                            {
                                throw new Exception("Unrecognized control encountered!");
                            }
                            if (!NoGUI)
                                tmpProgBar.Step();
                        }
                        //progDisplay.DestroyProgressBar(tmpProgBar);
                    }
                }

                #region Call of the reference reset functions
                #region Common message definitions message resets
                for (int i = 0; i < cmcDefinitios.AEUC_MSG.Count; i++)
                {
                    ((GenMSG)cmcDefinitios.AEUC_MSG[i]).ResetMessageControlTabReferences(TabPagesL);
                }
                for (int i = 0; i < cmcDefinitios.SPECMSG_MSG.Count; i++)
                {
                    ((GenMSG)cmcDefinitios.SPECMSG_MSG[i]).ResetMessageControlTabReferences(TabPagesL);
                }
                #endregion
                #region AEUC setting linking and auxiliary reference resets
                for (int i = 0; i < TabPagesNum; i++)
                {
                    for (int ctrReset = 0; ctrReset < TabPagesL[i].Controls.Count; ctrReset++)
                    {
                        if (TabPagesL[i].Controls[ctrReset] is IAEUCSetting)
                        {
                            ((IAEUCSetting)TabPagesL[i].Controls[ctrReset]).AEUC_ResetToDefault();
                            NoError = ((IAEUCSetting)TabPagesL[i].Controls[ctrReset]).AEUC_SetLinkInitialization();
                        }
                    }
                    //alignControls(TabPagesL[i]);
                }
                #endregion
                #endregion

                specCaseLoad = srReader.ReadInt32();
                if (specCaseLoad > -1)
                {
                    for (int i = 0; i < specCaseLoad; i++)
                    {
                        GenTabPageProperties tmpTPProp = new GenTabPageProperties(this);
                        NoError = tmpTPProp.Deserialize(srReader);
                        gtpProperties.Add(tmpTPProp);
                    }
                }
                else if (TabPagesNum > 0)
                {
                    MessageBox.Show("Error loading file, generatig default tab page properties.");
                    for (int i = 0; i < TabPagesNum; i++)
                    {
                        GenTabPageProperties tmpTPProp = new GenTabPageProperties(TabPagesL[i].Text, TabPagesL[i], this);
                        gtpProperties.Add(tmpTPProp);
                    }
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show("Error loading file: " + ex.Message);
            }
            finally
            {
                if (!NoGUI)
                    DoneDeserialization();
                else
                    DoneDeserializationNoUI();

                if (srReader != null)
                    srReader.Close();
            }
            return NoError;
        }
        #endregion
        #endregion
    }
}
